﻿using System;
using System.Net;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Documents;
using System.Windows.Ink;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Animation;
using System.Windows.Shapes;
using System.Collections.Generic;
using System.Collections.ObjectModel;

namespace SilverlightDragDrop
{
  public class DropTarget: ContentControl
  {
    private GroupCollection groups = new GroupCollection();
    public GroupCollection Groups { get { return groups; } set { groups = value; } }
    
    public delegate void OnDropHandler(object sender, DragDropEventArgs e);
    public event OnDropHandler OnDropped;
    public event OnDropHandler OnDraggedOver;
    public event OnDropHandler OnDraggedOut;

    public DropTarget()
    {
      this.MouseEnter += new MouseEventHandler(DropTarget_MouseEnter);
    }

    private void DropTarget_MouseEnter(object sender, MouseEventArgs e)
    {
      if (DragDrop.IsDragging)
      {
        var source = DragDrop.StopDragging();
        if (OnDropped != null && AcceptsGroups(source.Groups))
        {
          OnDropped(this, new DragDropEventArgs() { Source = source.Content });
        }
      }
    }

    internal void DraggedOver(DragSource source)
    {
      if (OnDraggedOver != null && AcceptsGroups(source.Groups))
      {
        OnDraggedOver(this, new DragDropEventArgs() { Source = source.Content });
      }
    }

    internal void DraggedOut(DragSource source)
    {
      if (OnDraggedOut != null && AcceptsGroups(source.Groups))
      {
        OnDraggedOut(this, new DragDropEventArgs() { Source = source.Content });
      }
    }

    private bool AcceptsGroups(GroupCollection groups)
    {
      // DropTarget with no groups accepts all dragsources
      if (this.Groups.Count == 0) return true;

      // Otherwise, it only accepts explicitly named groups
      foreach (var group in this.Groups)
      {
        if (groups.Contains(group)) return true;
      }

      // No matching group found, don't accept
      return false;
    }

  }
}
